home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Gold Medal Software 2
/
Gold Medal Software Volume 2 (Gold Medal) (1994).iso
/
prog
/
asm_0_m.arj
/
DISPLAY.ASM
< prev
next >
Wrap
Assembly Source File
|
1987-10-20
|
13KB
|
575 lines
TITLE DISPLAY
; by Douglas Clark and William C. Parke (c) Copyright 1987
;
; Quick display of a page of a file on screen with special attributes
;
PUBLIC START,BEGIN
CODE SEGMENT
ASSUME CS:CODE,DS:CODE
ORG 100H
;
CR EQU 0DH
LF EQU 0AH
;
START: JMP BEGIN
;
PAG_MAR DB '^' ; page marker
ATR_SYM DB '\' ; attribute symbol with start/stop codes
DB 14 DUP(0)
DB 1AH
FILNAM DB 80 DUP(0)
PAGIDF DB 0
DB 0
PAGIDS DW 0
PAGID DB 32 DUP(0)
FHAN DW 0
PAG_START DW 0
PAG_SIZ DW 0
VID_SEG DW 0B000H ; mono addr for direct video
PGPTR DW 0
PGADR DB 256 DUP(0)
HELP: AND AL,AL ; any error messages?
JZ HELP1
XOR AH,AH
PUSH AX
DEC AL
SHL AX,1
MOV BX,AX
MOV DX,WORD PTR ERR_TBL[BX]
MOV AH,9H
INT 21H
POP AX
MOV AH,4CH
INT 21H ; exit
HELP1: MOV DX,OFFSET DHELP
MOV AH,9
INT 21H
MOV AX,4C00H
INT 21H ; EXIT clean
BEGIN: CALL COMMAND_LN ; get screen file name and page id
JC HELP
CALL OPENF ; open screen file
JC HELP
CALL VID_MEM ; get video memory address
CALL READF
JC HELP
MOV SI,OFFSET PAGID
MOV DI,OFFSET FILBUF
MOV PAG_START,DI ; default begin address
MOV CX,WORD PTR FILBUFL
MOV PAG_SIZ,CX ; default size
TEST BYTE PTR PAGIDF,1 ; test if page id is present
JZ VID5 ; show whole file
CALL STRSEARCH ; look for page id
JC HELP
MOV PAG_START,DX ; save addr. of hit from search
MOV AX,DI
SUB AX,DX ; new size
JC HELP1
MOV PAG_SIZ,AX ; save new size
VID5: MOV SI,PAG_START ; SI->filbuf (or page therein)
MOV AX,SI
MOV DI,OFFSET PGADR
STOSW
XOR AX,AX
MOV CX,126
REP STOSW ; zero beyond first addr
MOV WORD PTR PGPTR,AX ; zero the initial page ptr
MOV AX,VID_SEG
MOV ES,AX
VIDR: MOV BX,PGPTR ; current page index into pgadr
MOV SI,WORD PTR PGADR[BX] ; get address of page
AND SI,SI
JNZ VIDRN
SUB BX,2
MOV PGPTR,BX
MOV SI,WORD PTR PGADR[BX]
VIDRN: CALL CLRSCN
MOV BX,DI ; save di
MOV DX,23 ; maximum lines
VID7: LODSB
VID7C: CMP AL,LF ; skip Line Feeds
JZ VID7
CMP AL,CR ; chk Carr.Ret.
JNZ VID8 ; no
MOV DI,BX ; yes
ADD DI,(80*2) ; bump to next line on screen
MOV BX,DI
DEC DX ; 23-row count
JNZ VID7
JMP SHORT VID9
VID8: CMP AL,1AH ; chk e-o-f
JZ VID9F
CMP AL,'\' ; control code?
JNZ VIDS
CMP BYTE PTR [SI],'\' ; cancel?
JZ VIDSC
CALL CODES
JMP SHORT VID7C
VIDSC: INC SI
VIDS: OR AL,0
OCMASK EQU $-1
STOSB
MOV AL,ATTRIB ; get attribute
STOSB ; store attrib.
JMP SHORT VID7 ; loop
VID9F: XOR SI,SI ; no more
MOV BX,PGPTR
AND BX,BX
JZ VID10
TEST BYTE PTR PAGIDF,1
JNZ VID10
VID9: MOV BX,PGPTR
INC BX ; next page
INC BX
MOV PGPTR,BX
MOV WORD PTR PGADR[BX],SI ; save ptr to next page
JMP SHORT VID16
VID9U: MOV BX,PGPTR
SUB BX,4
JNC VID9V
XOR BX,BX
VID9V: MOV PGPTR,BX
JMP VIDR
VID10: MOV AX,CS
MOV ES,AX ; restore ES
MOV AX,DI ; current screen byte count
XOR DX,DX
MOV CX,80*2 ; bytes for rows
DIV CX ; ax= rows, dx= remainder
SHR DX,1 ; column in dl
MOV DH,AL ; row in dh
MOV AH,02H ; locate
MOV BH,00H ; curr screen
INT 10H
MOV AX,4C00H
INT 21H ; terminate program
VID16: MOV AH,0
INT 16H
CMP AX,5100H ; PgDn
JZ VID16R
CMP AX,4900H ; PgUp
JZ VID9U
CMP AX,011BH ; esc
JZ VID10
CMP AX,2E03H ; ^C
JZ VID10
CMP AX,4700H ; home
JZ VIDHOM
CMP AX,4F00H ; end
JZ VIDEND
JMP SHORT VID16
VID16R: JMP VIDR
VIDHOM: MOV WORD PTR PGPTR,0
JMP VIDR
VIDEND: XOR AX,AX
MOV BX,AX
SUB BX,2
MOV CX,129
VIDENS: ADD BX,2
CMP WORD PTR PGADR[BX],AX ; look for first zero address
LOOPNZ VIDENS
JCXZ VID10
SUB BX,2 ; addr just before is 'end' one
MOV PGPTR,BX ; use counter for ptr
JMP VIDR
;
;---------------------------------------------------------------
STRSEARCH:
; Input: SI= pagid string Output: DX= found page position
; DI= file buffer DI= end of page pointer
; CX= file buffer size
;---------------------------------------------------------------
CLD ;forward direction
STRSR0: CALL SYMSEARCH ; search for pag symbol
JNC STRSR1
MOV AL,3 ; error: no page symbol
RET
STRSR1: PUSH CX ; save buffer length
MOV CX,PAGIDS
INC CX
PUSH SI
REPZ CMPSB ; search for page id
POP SI
AND CX,CX ; did we find it?
POP CX ; get back file length remaining
JNZ STRSR0 ; not yet
MOV DX,DI ; save address of first page
CALL SYMSEARCH
DEC DI
MOV WORD PTR [DI-1],1A1AH
XOR AX,AX
RET
SYMSEARCH:
; find page break symbol in buffer
MOV AL,PAG_MAR
SYMSR0: REPNZ SCASB
AND CX,CX
JNZ SYMSR2
SYMSR1:
STC
RET
SYMSR2:
DEC CX
JZ SYMSR1
SCASB
JNZ SYMSR0
RET
;---------------------------------------------------------------
COMMAND_LN:
; Input: none Output: Command line file name in FILNAM
; Page code in PAGID
;---------------------------------------------------------------
MOV SI,80H ; get command string buffer
LODSB ; get command string size
AND AL,AL ; anything there?
JNZ CMDLN1 ; ok, there is a string
XOR AL,AL ; no error message
STC
RET
CMDLN1: XOR CH,CH ; zero ch
MOV CL,AL ; put size in cx
INC CX
MOV DI,OFFSET FILNAM ; buffer for asciz filename
CMDLN2: LODSB ; get byte from command string
CMP AL,20H ; see if its a space
LOOPZ CMDLN2 ; skip if so
AND CX,CX ; are we at end of string?
JNZ CMDLNL ; not yet
CMDLNS: XOR AL,AL ; no error message
STC
RET
CMDLNL: STOSB ; save file name byte
LODSB ; get next byte
CMP AL,'/' ; switch?
JNZ CMDLN4 ; no
XOR AL,AL
STOSB
DEC CX
JMP SHORT CMDLNA ; look for page number
CMDLNT: XOR AL,AL
STOSB
RET
CMDLN4: CMP AL,20H ; space?
JZ CMDLN5
CMP AL,CR
JZ CMDLNT
CMP AL,';'
LOOPNZ CMDLNL
JMP SHORT CMDLNT
CMDLN5: XOR AL,AL
STOSB
JCXZ CMDLNT
CMDLN8: LODSB
CMP AL,20H
JZ CMDLN9
CMP AL,';'
JZ CMDLNT
CMP AL,CR
JZ CMDLNT
CMP AL,'/'
JZ CMDLNA
CMDLN9: LOOP CMDLN8
JMP SHORT CMDLNT
CMDLNA: CMP CX,3
JC CMDLNM
CMDLNC: LODSW ; get '=p'
SUB CX,2
AND AL,5FH
CMP AX,3D50H
JZ CMDLND
CMDLNM: MOV AL,1 ; invalid switch
STC
RET
CMDLND: MOV DI,OFFSET PAGID
XOR BX,BX ; count of pagid
CMDLNF: LODSB
CMP AL,' '
JZ CMDLNE
CMP AL,CR
JZ CMDLNE
CMP AL,';'
JZ CMDLNE
INC BX
STOSB
LOOP CMDLNF ; save page id
CMDLNE: MOV AL,PAG_MAR
STOSB ; add ^^ to end
INC BX
STOSB
INC BX
MOV PAGIDS,BX ; save size of id
MOV BYTE PTR PAGIDF,1 ; set flag
XOR AX,AX
STOSB
RET
;---------------------------------------------------------------
OPENF:
; Input: none Output: File handle in FHAN
;---------------------------------------------------------------
MOV DX,OFFSET FILNAM ; DX -> input file name
MOV AX,3D00H ; open for input
INT 21H
JNC OPN1
MOV AL,2 ; error opening file
RET
OPN1: MOV FHAN,AX ; save handle
RET
;---------------------------------------------------------------
CLRSCN:
; Input: none Output: none
;---------------------------------------------------------------
MOV CX,0000H ; row,col
MOV DX,184FH ; row,col
MOV AX,0600H ; CLS clear screen
MOV BH,07H ; normal
INT 10H
MOV DX,1800H ; column in dl, row in dh
MOV AH,02H ; locate
MOV BH,00H ; curr screen
INT 10H
XOR DI,DI ; start at top of screen
RET
;---------------------------------------------------------------
VID_MEM:
; Input: none Output: Active video memory address in VID_SEG
;---------------------------------------------------------------
MOV AX,40H ; bios data segment
PUSH DS
MOV DS,AX ; DS -> bios data seg.
CMP WORD PTR DS:63H,03B4H ; If Mono... (everex-cga=03D4 )
POP DS
JZ VIDM1
ADD WORD PTR VID_SEG,0800H ; adj. for CGA
VIDM1: RET
;---------------------------------------------------------------
READF:
; Input: none Output: FILBUF filled with file of length FILBUFL
;---------------------------------------------------------------
MOV DX,OFFSET FILBUF ; DX -> file buffer
MOV AX,3F00H ;
MOV BX,FHAN
MOV CX,0C000H ; Read 48k
INT 21H ;
JNC READ11
MOV AL,4 ; bad read
RET
READ11:
MOV WORD PTR FILBUFL,AX ; save length of file
ADD AX,DX ; append
DEC AX ; ^Z (eof)
MOV BX,AX ; to the end
MOV WORD PTR [BX],1A1AH ; of the data.
MOV BX,FHAN
MOV AX,3E00H ; close handle
INT 21H
RET
;---------------------------------------------------------------
CODES:
; Input: SI=file buffer at /+1 Output: set attribute of AL
;---------------------------------------------------------------
MOV AL,[SI] ; get /+1 char
PUSH CX ; save cx
PUSH DI ; save di
PUSH ES
PUSH DS
POP ES
MOV DI,OFFSET COD_TBL ; point to / codes
MOV CX,17
REPNZ SCASB
POP ES
POP DI
AND CX,CX
MOV AH,CL ; save 16-count in ah
POP CX
JNZ CODE1 ; jmp if we found one
RET ; return with orig. char
CODE1: INC SI ; point to /+2
PUSH BX ; save bx
MOV BX,16
SUB BL,AH
CMP BX,8
JNC CODOFF ; must be a lower case off switch
AND BX,BX
JZ CODET ; if its zero, must be A switch
CMP BX,6
JNC CODEC ; if its above 5, must be color
MOV AL,COD_MSK[BX] ; get mask
CMP BL,5
JNC CODAH ; a hide request
CMP BL,3
JC CODOA ; A, I, or B request
SUB BL,3
JZ CODAA ; process U request
OR BYTE PTR ATTRIB,AL
MOV AL,11111000B ; and for reverse
CODAA: AND BYTE PTR ATTRIB,AL
POP BX
LODSB ; get /+2 char
RET
CODOA: OR BYTE PTR ATTRIB,AL ; turn on attribute requested
POP BX
LODSB
RET
CODAH: MOV AL,BYTE PTR ATTRIB
MOV ATTRH,AL ; save a copy of the attr byte
MOV BYTE PTR ATTRIB,0
POP BX
LODSB
RET
CODOH: MOV AL,BYTE PTR ATTRH
AND AL,AL ; test if non-zero
JNZ CODOH1
MOV AL,07H ; use default attribute
CODOH1: MOV BYTE PTR ATTRIB,AL ; restore copy of attr byte
POP BX
LODSB
RET
CODET: MOV BYTE PTR OCMASK,10000000B
POP BX
LODSB
RET
CODEU: MOV BYTE PTR OCMASK,00000000B
POP BX
LODSB
RET
CODOFF: SUB BX,8 ; get displacement for off switch
JZ CODEU ; request to turn off alter. char.
CMP BX,6
JNC CODEC ; color request
MOV AL,COD_MSK[BX] ; get mask
NOT AL ; reverse bits
CMP BL,5
JNC CODOH ; or attribute to unhide
CMP BL,3
JC CODAA ; A, I, or B request
SUB BL,3
JZ CODOA ; process U request
AND BYTE PTR ATTRIB,AL
MOV AL,00000111B ; or for reverse off
JMP SHORT CODOA
CODEC: MOV BYTE PTR SHIFT,0 ; assume foreground
SUB BL,6 ; see if C or S
JZ CODESS ; do foreground Char. color
MOV BYTE PTR SHIFT,4 ; set up background S shift
CODESS: MOV AL,[SI] ; get /+2
OR AL,' ' ; make lower case
PUSH DI
PUSH ES
PUSH DS
POP ES
PUSH CX
MOV DI,OFFSET COLOR_T
MOV CX,8
REPNZ SCASB
AND CX,CX
MOV AH,CL
POP CX
POP ES
POP DI
JZ CODESE
INC SI ; point to /+3
MOV BX,7
SUB BL,AH
MOV AL,COLOR_M[BX] ; get color bit mix
MOV AH,11111000B ; mask for foreground
TEST BYTE PTR SHIFT,4
JZ CODESU ; no shift needed for foreground
PUSH CX
XOR CX,CX
MOV CL,SHIFT
SHL AL,CL
POP CX
MOV AH,10001111B ; mask for background
CODESU: AND BYTE PTR ATTRIB,AH
OR BYTE PTR ATTRIB,AL
POP BX
LODSB ; get next real character
RET
CODESE: DEC SI
POP BX
MOV AL,[SI] ; restore /+1 char.
RET
ATTRIB DB 7 ; normal attribute
ATTRH DB 0
COD_TBL DB 'AIBURHCS'
DB 'aiburhcs',0
COLOR_T DB 'bgtrvpw',0,0
COD_MSK DB 10000000B ; alternate char. set bit or
DB 00001000B ; intensity bit or
DB 10000000B ; blinking bit or
DB 11111001B ; underline bit and
DB 01110000B ; reverse video bits and
DB 00000000B ; hide byte and
DB 00000111B ; foreground bits
DB 01110000B ; background bits
COLOR_M DB 00000001B ; blue
DB 00000010B ; green
DB 00000011B ; turquoise
DB 00000100B ; red
DB 00000101B ; violet
DB 00000110B ; pink
DB 00000111B ; white
SHIFT DB 0
DW 0
ERR_TBL DW ERRSW
DW NOFILE
DW NOPAGE
DW ERREAD
ERRSW DB CR,LF,'Invalid switch on command line.',CR,LF,'$'
NOFILE DB CR,LF,'Cannot open file.',CR,LF,'$'
NOPAGE DB CR,LF,'Page Not Found.',CR,LF,'$'
ERREAD DB CR,LF,'Error reading file.',CR,LF,'$'
MARKEND EQU $
DHELP DB CR,LF
DB ' DISPLAY Version 1.1',CR,LF
DB ' ',CR,LF
DB ' A fast file to screen displayer',CR,LF
DB ' by Douglas Clark and W.C. Parke',CR,LF
DB ' (c) 1987',CR,LF
DB ' ',CR,LF
DB 'Syntax: DISPLAY filename [/P=pageid]',CR,LF
DB ' where filename is a valid file to display,',CR,LF
DB ' pageid is a page identification string',CR,LF
DB ' embedded in the file, with a pair of',CR,LF
DB ' carots (^^) on prefix and suffix.',CR,LF
DB ' Embed ''\x'' controls in text for enhanced text:',CR,LF
DB ' Monochrome: Start Stop Color: Character Screen',CR,LF
DB ' hide \H \h blue \cb \sb',CR,LF
DB ' underline \U \u green \cg \sg',CR,LF
DB ' reverse video \R \r turquoise \ct \st',CR,LF
DB ' blinking \B \b red \cr \sr',CR,LF
DB ' intense \I \i violet \cv \sv',CR,LF
DB ' alternate ibm- pink \cp \sp',CR,LF
DB ' character set \A \a white \cw \sw',CR,LF,'$'
FILBUFL EQU MARKEND ; length of file
FILBUF EQU FILBUFL+2 ; 1st 48k of file
;
CODE ENDS
END START